package com.cskaoyan.service;

import com.cskaoyan.bean.*;
import com.cskaoyan.bean.common.BasePageInfo;
import com.cskaoyan.bean.common.CommonData;
import com.cskaoyan.bean.vo.WxCouponListVo;
import com.cskaoyan.bean.vo.WxCouponMylistVo;
import com.cskaoyan.mapper.MarketCartMapper;
import com.cskaoyan.mapper.MarketCouponMapper;
import com.cskaoyan.mapper.MarketCouponUserMapper;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import org.apache.shiro.SecurityUtils;
import org.apache.shiro.subject.Subject;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.math.BigDecimal;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.concurrent.atomic.AtomicReference;
import java.util.stream.Collectors;

/**
 * @Author: JianhuaZeng
 * @Date: 2023/1/2 10:53
 */
@Service
public class WxCouponServiceImpl implements WxCouponService {

    @Autowired
    MarketCouponMapper couponMapper;

    @Autowired
    MarketCouponUserMapper couponUserMapper;

    @Autowired
    MarketCartMapper cartMapper;

    @Override
    public CommonData list(BasePageInfo pageInfo) {
        PageHelper.startPage(pageInfo.getPage(), pageInfo.getLimit());
        MarketCouponExample couponExample = new MarketCouponExample();
        MarketCouponExample.Criteria criteria = couponExample.createCriteria();
        criteria.andDeletedEqualTo(false);
        couponExample.setOrderByClause("id");
        List<MarketCoupon> couponList = couponMapper.selectByExample(couponExample);
        List<WxCouponListVo> couponListVos = couponList.stream()
                .map(o -> new WxCouponListVo(o.getId(), o.getName(), o.getDiscount(), o.getMin(), (int) o.getDays(),
                        o.getDesc(), o.getTag()))
                .collect(Collectors.toList());
        PageInfo<WxCouponListVo> couponListVoPageInfo = new PageInfo<>(couponListVos);
        return CommonData.data(couponListVoPageInfo);
    }

    @Override
    public CommonData myList(Short status, Integer page, Integer limit) {
        PageHelper.startPage(page, limit);

        MarketCouponUserExample couponUserExample = new MarketCouponUserExample();
        MarketCouponUserExample.Criteria criteria = couponUserExample.createCriteria();
        criteria.andUserIdEqualTo(getUserId());
        criteria.andDeletedEqualTo(false);
        criteria.andStatusEqualTo(status);
        List<MarketCouponUser> couponUsers = couponUserMapper.selectByExample(couponUserExample);

        List<WxCouponMylistVo> couponListVos = new ArrayList<>();
        for (MarketCouponUser couponUser : couponUsers) {
            WxCouponMylistVo couponMylistVo = castCouponUserToCouponMylistVo(couponUser);
            couponListVos.add(couponMylistVo);
        }
        return CommonData.data(new PageInfo<>(couponListVos));
    }

    /**
     * @description: 返回 0:优惠券不存在 1:领取成功
     * @param: code
     * @return: java.lang.Integer
     * @author: JianhuaZeng
     * @date: 2023/1/2 2023/1/2
     */
    public Integer exchange(String code) {
        MarketCouponExample couponExample = new MarketCouponExample();
        MarketCouponExample.Criteria criteria = couponExample.createCriteria();
        criteria.andDeletedEqualTo(false);
        criteria.andCodeEqualTo(code);
        List<MarketCoupon> coupons = couponMapper.selectByExample(couponExample);
        if (coupons.size() == 0) {
            return 0;
        }

        MarketCoupon coupon = coupons.get(0);
        Date date = new Date();
        Integer userId = getUserId();

        MarketCouponUser couponUser = new MarketCouponUser();
        couponUser.setUserId(userId);
        couponUser.setCouponId(coupon.getId());
        couponUser.setStatus((short) 0);
        couponUser.setStartTime(coupon.getStartTime());
        couponUser.setEndTime(coupon.getEndTime());
        couponUser.setAddTime(date);
        couponUser.setUpdateTime(date);
        couponUser.setDeleted(false);
        couponUserMapper.insertSelective(couponUser);
        return 1;
    }

    /**
     * @description: 返回 0:优惠券已领取过 1:领取优惠券成功
     * @param: couponId
     * @return: java.lang.Integer
     * @author: JianhuaZeng
     * @date: 2023/1/2 2023/1/2
     */
    public Integer receive(Integer couponId) {
        Integer userId = getUserId();
        MarketCouponUserExample couponUserExample = new MarketCouponUserExample();
        MarketCouponUserExample.Criteria criteria = couponUserExample.createCriteria();
        criteria.andUserIdEqualTo(userId);
        criteria.andCouponIdEqualTo(couponId);
        long count = couponUserMapper.countByExample(couponUserExample);
        if (count == 0) {
            // 领取优惠券

            MarketCoupon coupon = couponMapper.selectByPrimaryKey(couponId);
            Date date = new Date();

            MarketCouponUser couponUser = new MarketCouponUser();
            couponUser.setUserId(userId);
            couponUser.setCouponId(couponId);
            couponUser.setStatus((short) 0);
            couponUser.setStartTime(coupon.getStartTime());
            couponUser.setEndTime(coupon.getEndTime());
            couponUser.setAddTime(date);
            couponUser.setUpdateTime(date);
            couponUser.setDeleted(false);
            couponUserMapper.insertSelective(couponUser);
            return 1;
        }
        // 优惠券已领取过
        return 0;
    }

    /**
     * @description: 查询用户购物车中的优惠券
     * @param: cartId
     * @param: grouponRulesId
     * @return: com.cskaoyan.bean.common.CommonData
     * @author: JianhuaZeng
     * @date: 2023/1/3 2023/1/3
     */
    public CommonData selectList(Integer cartId, Integer grouponRulesId) {

        // 记录购物车中所有商品的总价
        BigDecimal total = BigDecimal.valueOf(0);

        MarketCartExample cartExample = new MarketCartExample();
        MarketCartExample.Criteria cartCriteria = cartExample.createCriteria();
        cartCriteria.andDeletedEqualTo(false);
        cartCriteria.andCheckedEqualTo(true);
        List<MarketCart> carts;
        if (cartId != 0) {
            // 查询一条购物车记录
            cartCriteria.andIdEqualTo(cartId);
             carts = cartMapper.selectByExample(cartExample);
            if (carts.size()!=0){
                total = total.add(carts.get(0).getPrice());
            }
        }else {
            // cart = 0 查询该用户的所有的购物车记录
            cartCriteria.andUserIdEqualTo(getUserId());
            carts = cartMapper.selectByExample(cartExample);
            for (MarketCart cart : carts) {
                total = total.add(cart.getPrice());
            }
        }

        // 查询用户的优惠券并筛选出满足 商品总价 total > min 的优惠券
        MarketCouponUserExample couponUserExample = new MarketCouponUserExample();
        MarketCouponUserExample.Criteria criteria = couponUserExample.createCriteria();
        criteria.andUserIdEqualTo(getUserId());
        criteria.andDeletedEqualTo(false);
        criteria.andStatusEqualTo((short) 0);
        List<MarketCouponUser> couponUsers = couponUserMapper.selectByExample(couponUserExample);

        List<WxCouponMylistVo> couponListVos = new ArrayList<>();
        for (MarketCouponUser couponUser : couponUsers) {
            // 判断优惠券的min是否>=total
            BigDecimal min = couponMapper.selectByPrimaryKey(couponUser.getCouponId()).getMin();
            if(min.compareTo(total)>0){
                continue;
            }
            WxCouponMylistVo couponMylistVo = castCouponUserToCouponMylistVo(couponUser);
            couponListVos.add(couponMylistVo);
        }

        CommonData commonData = new CommonData();
        commonData.setPage(1);
        commonData.setLimit(couponListVos.size());
        commonData.setPages(1);
        commonData.setTotal(couponListVos.size());
        commonData.setList(couponListVos);
        return commonData;


    }

    private Integer getUserId() {
        // 获取当前用户id
        Subject subject = SecurityUtils.getSubject();
        MarketUser principal = (MarketUser) subject.getPrincipal();
        Integer userId = principal.getId();
        return userId;
    }

    /**
     * @description: 把MarketCouponUser对象映射成WxCouponMylistVo对象
     * @param: couponUser
     * @return: com.cskaoyan.bean.vo.WxCouponMylistVo
     * @author: JianhuaZeng
     * @date: 2023/1/3 2023/1/3
     */
    private WxCouponMylistVo castCouponUserToCouponMylistVo(MarketCouponUser couponUser) {
        MarketCoupon coupon = couponMapper.selectByPrimaryKey(couponUser.getCouponId());

        // 判断优惠券是否过期
        Boolean availabel = false;
        Date date = new Date();
        if (coupon.getStatus() == 0) {
            availabel = true;
        }

        WxCouponMylistVo mylistVo = new WxCouponMylistVo();
        mylistVo.setId(couponUser.getId());
        mylistVo.setName(coupon.getName());
        mylistVo.setDiscount(coupon.getDiscount());
        mylistVo.setMin(coupon.getMin());
        mylistVo.setDesc(coupon.getDesc());
        mylistVo.setTag(coupon.getTag());
        mylistVo.setEndTime(coupon.getEndTime());
        mylistVo.setStartTime(coupon.getStartTime());
        mylistVo.setAvailable(availabel);
        mylistVo.setCid(coupon.getId());
        return mylistVo;
    }
}
